home *** CD-ROM | disk | FTP | other *** search
/ GFX Sensations 1 / Graphic Sensations - Volume 1.iso / tools / amiga / 3d_tools / irit40s.lha / Irit / cagd_lib / sbspeval.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-12-30  |  5.2 KB  |  163 lines

  1. /******************************************************************************
  2. * SBspEval.c - Bspline surfaces handling routines - evaluation routines.      *
  3. *******************************************************************************
  4. * Written by Gershon Elber, Mar. 90.                          *
  5. ******************************************************************************/
  6.  
  7. #include <string.h>
  8. #include "cagd_loc.h"
  9.  
  10. /******************************************************************************
  11. * Evaluate the given tensor product Bspline surface at a given point, by      *
  12. * extracting an isoparamteric curve along u and evaluating v in it.          *
  13. *                                          *
  14. *        u -->                                  *
  15. *     +----------------------+                              *
  16. *     |P0         Pi-1|                              *
  17. *   V |Pi        P2i-1|    Parametric space orientation - control mesh.  *
  18. *    ||                 |                              *
  19. *    v|Pn-i         Pn-1|                              *
  20. *     +----------------------+                              *
  21. *                                          *
  22. ******************************************************************************/
  23. CagdRType *BspSrfEvalAtParam(CagdSrfStruct *Srf, CagdRType u, CagdRType v)
  24. {
  25.     CagdRType *Pt;
  26.     CagdCrvStruct
  27.     *IsoCrv = BspSrfCrvFromSrf(Srf, u, CAGD_CONST_U_DIR);
  28.  
  29.     if (!BspKnotParamInDomain(IsoCrv -> KnotVector, IsoCrv -> Length,
  30.                             IsoCrv -> Order, v))
  31.     FATAL_ERROR(CAGD_ERR_V_NOT_IN_SRF);
  32.  
  33.     Pt = BspCrvEvalAtParam(IsoCrv, v);
  34.  
  35.     CagdCrvFree(IsoCrv);
  36.  
  37.     return Pt;
  38. }
  39.  
  40. /******************************************************************************
  41. * Extract an isoline curve out of the given tensor product Bspline surface.   *
  42. * Operations should prefer the CONST_U_DIR, in which the extraction is          *
  43. * somewhat faster if it is possible.                          *
  44. ******************************************************************************/
  45. CagdCrvStruct *BspSrfCrvFromSrf(CagdSrfStruct *Srf, CagdRType t,
  46.                             CagdSrfDirType dir)
  47. {
  48.     CagdCrvStruct
  49.     *Crv = NULL;
  50.     CagdBType
  51.     IsNotRational = !CAGD_IS_RATIONAL_SRF(Srf);
  52.     int i, j, CrvLen,
  53.     MaxCoord = CAGD_NUM_OF_PT_COORD(Srf -> PType);
  54.     CagdRType *CrvP, *SrfP;
  55.  
  56.     switch (dir) {
  57.     case CAGD_CONST_U_DIR:
  58.         if (!BspKnotParamInDomain(Srf -> UKnotVector, Srf -> ULength,
  59.                               Srf -> UOrder, t))
  60.         FATAL_ERROR(CAGD_ERR_U_NOT_IN_SRF);
  61.         Crv = BspCrvNew(CrvLen = Srf -> VLength,
  62.                 Srf -> VOrder, Srf -> PType);
  63.         CAGD_GEN_COPY(Crv -> KnotVector, Srf -> VKnotVector,
  64.               sizeof(CagdRType) * (Srf -> VLength + Srf -> VOrder));
  65.  
  66.         for (i = IsNotRational; i <= MaxCoord; i++) {
  67.         CrvP = Crv -> Points[i];
  68.         SrfP = Srf -> Points[i];
  69.         for (j = 0; j < CrvLen; j++) {
  70.             *CrvP++ = BspCrvEvalVecAtParam(SrfP, CAGD_NEXT_U(Srf),
  71.                        Srf -> UKnotVector, Srf -> UOrder,
  72.                        Srf -> ULength, t);
  73.             SrfP += CAGD_NEXT_V(Srf);
  74.         }
  75.         }
  76.         break;
  77.     case CAGD_CONST_V_DIR:
  78.         if (!BspKnotParamInDomain(Srf -> VKnotVector, Srf -> VLength,
  79.                               Srf -> VOrder, t))
  80.         FATAL_ERROR(CAGD_ERR_V_NOT_IN_SRF);
  81.         Crv = BspCrvNew(CrvLen = Srf -> ULength,
  82.                 Srf -> UOrder, Srf -> PType);
  83.         CAGD_GEN_COPY(Crv -> KnotVector, Srf -> UKnotVector,
  84.               sizeof(CagdRType) * (Srf -> ULength + Srf -> UOrder));
  85.  
  86.         for (i = IsNotRational; i <= MaxCoord; i++) {
  87.         CrvP = Crv -> Points[i];
  88.         SrfP = Srf -> Points[i];
  89.         for (j = 0; j < CrvLen; j++) {
  90.             *CrvP++ = BspCrvEvalVecAtParam(SrfP, CAGD_NEXT_V(Srf),
  91.                        Srf -> VKnotVector, Srf -> VOrder,
  92.                        Srf -> VLength, t);
  93.             SrfP += CAGD_NEXT_U(Srf);
  94.         }
  95.         }
  96.         break;
  97.     default:
  98.         FATAL_ERROR(CAGD_ERR_DIR_NOT_CONST_UV);
  99.         break;
  100.     }
  101.     return Crv;
  102. }
  103.  
  104. /******************************************************************************
  105. * Extract an isoline curve out of the given mesh row/col.              *
  106. * The provided (zero based) Index specifies which row/col Index to extract.   *
  107. ******************************************************************************/
  108. CagdCrvStruct *BspSrfCrvFromMesh(CagdSrfStruct *Srf, int Index,
  109.                             CagdSrfDirType Dir)
  110. {
  111.     CagdCrvStruct
  112.     *Crv = NULL;
  113.     CagdBType
  114.     IsNotRational = !CAGD_IS_RATIONAL_SRF(Srf);
  115.     int i, j, CrvLen,
  116.     MaxCoord = CAGD_NUM_OF_PT_COORD(Srf -> PType);
  117.     CagdRType *CrvP, *SrfP;
  118.  
  119.     switch (Dir) {
  120.     case CAGD_CONST_U_DIR:
  121.         if (Index + 1 > Srf -> ULength)
  122.         FATAL_ERROR(CAGD_ERR_INDEX_NOT_IN_MESH);
  123.  
  124.         Crv = BspCrvNew(CrvLen = Srf -> VLength,
  125.                 Srf -> VOrder, Srf -> PType);
  126.         CAGD_GEN_COPY(Crv -> KnotVector, Srf -> VKnotVector,
  127.               sizeof(CagdRType) * (Srf -> VLength + Srf -> VOrder));
  128.  
  129.         for (i = IsNotRational; i <= MaxCoord; i++) {
  130.         CrvP = Crv -> Points[i];
  131.         SrfP = Srf -> Points[i] + Index * CAGD_NEXT_U(Srf);
  132.         for (j = 0; j < CrvLen; j++) {
  133.             *CrvP++ = *SrfP;
  134.             SrfP += CAGD_NEXT_V(Srf);
  135.         }
  136.         }
  137.         break;
  138.     case CAGD_CONST_V_DIR:
  139.         if (Index + 1 > Srf -> VLength)
  140.         FATAL_ERROR(CAGD_ERR_INDEX_NOT_IN_MESH);
  141.  
  142.         Crv = BspCrvNew(CrvLen = Srf -> ULength,
  143.                 Srf -> UOrder, Srf -> PType);
  144.         CAGD_GEN_COPY(Crv -> KnotVector, Srf -> UKnotVector,
  145.               sizeof(CagdRType) * (Srf -> ULength + Srf -> UOrder));
  146.  
  147.         for (i = IsNotRational; i <= MaxCoord; i++) {
  148.         CrvP = Crv -> Points[i];
  149.         SrfP = Srf -> Points[i] + Index * CAGD_NEXT_V(Srf);;
  150.         for (j = 0; j < CrvLen; j++) {
  151.             *CrvP++ = *SrfP;
  152.             SrfP += CAGD_NEXT_U(Srf);
  153.         }
  154.         }
  155.         break;
  156.     default:
  157.         FATAL_ERROR(CAGD_ERR_DIR_NOT_CONST_UV);
  158.         break;
  159.     }
  160.     return Crv;
  161. }
  162.  
  163.